package example.service.dao;

import java.util.List;

import javax.persistence.EntityManager;
import javax.persistence.PersistenceContext;
import javax.persistence.Query;

import org.hibernate.Criteria;
import org.hibernate.Session;
import org.springframework.transaction.annotation.Transactional;

import example.service.dto.Person;

/**
 * Implementaci�n del dao de personas
 * 
 * "@Transactional" hace que los m�todos se ejecuten como transacciones.
 * @author icasado
 *
 */
@Transactional
public class PersonServiceImpl implements PersonService {
	
	// @PersistenceContext le dice a Spring que inyecte un EntityManager en el
	// servicio cuando se instancia.
    @PersistenceContext
    private EntityManager em;

    /**
     * Setter para EntityManager
     * @param em
     */
    public void setEntityManager(EntityManager em) {
        this.em = em;
    }

    private EntityManager getEntityManager() {
        return this.em;
    }

    /**
     * @see example.service.dao.PersonService#findAll()
     * @return List<Person> 
     */
    @SuppressWarnings("unchecked")
    public List<Person> findAll() {
        Query query = getEntityManager().createQuery("select p FROM Person p");
        return query.getResultList();
    }
    
    /**
     * @see example.service.dao.PersonService#findAllCriteria()
     * @return List<Person>
     */
    @SuppressWarnings("unchecked")
    public List<Person> findAllCriteria() {
        Criteria criteria = ((Session) getEntityManager().getDelegate())
				.createCriteria(Person.class);
        return criteria.list();
    }

    /**
     * @see example.service.dao.PersonService#save(example.service.dto.Person)
     */
    public void save(Person person) {
        if (person.getId() == null) {
            // new
            this.em.persist(person);
        } else {
            // update
            this.em.merge(person);
        }
    }
    
    /**
     * @see example.service.dao.PersonService#remove(int)
     */
    public void remove(int id) {
        Person person = find(id);
        if (person != null) {
            this.em.remove(person);
        }
    }

    /**
     * @see example.service.dao.PersonService#find(int)
     */
    public Person find(int id) {
        return this.em.find(Person.class, Integer.valueOf(id));
    }

}